import Item from "./Item";


const { ccclass, property } = cc._decorator;

@ccclass
export default class FrameLoading extends cc.Component {

    @property(cc.Node)
    content: cc.Node = null;

    @property(cc.Prefab)
    itemPrefab: cc.Prefab = null;


    _isFrameLoading: boolean = false;


    // onLoad () {}

    start() {

    }


    commonLoadItems() {
        this.content.destroyAllChildren();
        for (let i = 0; i < 500; i++) {
            let item = cc.instantiate(this.itemPrefab);
            item.parent = this.content;
            item.getComponent(Item).setData(i);
        }
    }

    async frameLoadingItems() {
        await this.frameLoading();
    }

    async frameLoading() {
        if (this._isFrameLoading) {
            return;
        }
        this._isFrameLoading = true;
        this.content.destroyAllChildren();
        await this.executePreFrame(this._getItemGenerator(500), 1);
    }


    private _initItem(itemIndex: number) {
        let itemNode = cc.instantiate(this.itemPrefab);
        itemNode.parent = this.content;
        itemNode.getComponent(Item).setData(itemIndex);
    }


    private executePreFrame(generator: Generator, duration: number) {
        return new Promise((resolve, reject) => {
            let gen = generator;
            // 创建执行函数
            let execute = () => {
                // 执行之前，先记录开始时间
                let startTime = new Date().getTime();

                // 然后一直从 Generator 中获取已经拆分好的代码段出来执行
                for (let iter = gen.next(); ; iter = gen.next()) {
                    // 判断是否已经执行完所有 Generator 的小代码段，如果是的话，那么就表示任务完成
                    if (iter == null || iter.done) {
                        resolve();
                        return;
                    }

                    // 每执行完一段小代码段，都检查一下是否已经超过我们分配的本帧，这些小代码端的最大可执行时间
                    if (new Date().getTime() - startTime > duration) {
                        // 如果超过了，那么本帧就不在执行，开定时器，让下一帧再执行
                        this.scheduleOnce(() => {
                            execute();
                        });
                        return;
                    }
                }
            };

            // 运行执行函数
            execute();
        });
    }

    private *_getItemGenerator(length: number) {
        for (let i = 0; i < length; i++) {
            yield this._initItem(i);
        }

        this._isFrameLoading = false;
    }

}
    // update (dt) {}
}
